package com.db.gffxo.epi.controller;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;

import org.apache.log4j.Logger;
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
import org.springframework.context.ApplicationContext;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;


import com.db.gffxo.epi.domain.Event;
import com.db.gffxo.epi.domain.EventDetail;
import com.db.gffxo.epi.domain.EventFormat;
import com.db.gffxo.epi.repository.EventDao;
import com.db.gffxo.epi.repository.EventFormatDao;
import com.db.gffxo.epi.repository.EventDetailDao;
import com.db.gffxo.epi.format.Formatter;

public class FormatControllerServicesImpl implements FormatControllerServices {
	
	
	private Logger log = Logger.getLogger(FormatControllerServicesImpl.class);

	EventDao eventDao = null;
	EventFormatDao eventFormatDao = null;
	EventDetailDao eventDetailDao = null;
	String ourTypes = new String();
		
	HashMap<String,ArrayList<Formatter>> formatters = new HashMap<String,ArrayList<Formatter>>();
		

	public List<Event> getEventBatch() {
		
		return eventDao.getEventbyStatusType(Event.STATUS_New, ourTypes, 10);	
	}
	
	public ArrayList<Formatter> getFormatter (String eventType) {
		return formatters.get(eventType);
		
	}
	
	@Transactional(propagation=Propagation.REQUIRED,rollbackFor=Exception.class,readOnly=false)
	public void updateFormattedEvent (Event event, String message, String formatterId, boolean success) {
		
		if (success) {
			eventDao.updateStatus(event);			
			EventDetail ed = new EventDetail();
			ed.setEventId(event.getEventId());
			ed.setMessage(message);
			ed.setFormatterId(formatterId);
			eventDetailDao.insert(ed);
		} else {
			event.setStatus(Event.STATUS_FailFormat);
			eventDao.updateStatus(event);						
		}
	}
	
	
	/* (non-Javadoc)
	 * @see com.db.gffxo.epi.controller.FormatControllerServices#loadFormatters()
	 */
	public void loadFormatters(ApplicationContext applicationContext) {
		
		List<EventFormat> allTypes = eventFormatDao.getEventFormat();
		Iterator<EventFormat> it = allTypes.iterator();
		StringBuffer theseTypes = new StringBuffer("\'");
		String lastType = "";
		ArrayList<Formatter> these = new ArrayList<Formatter>();
		while (it.hasNext()) {
			EventFormat ef = it.next();
			//Get formatter from application context
			try {
				Formatter fmt = (Formatter) applicationContext.getBean(ef.getFormatterName());
				fmt.configureFormatter(ef.getFormatterId());
				if (!lastType.equals(ef.getEventType())&&!lastType.equals("")) {
					formatters.put(lastType, these);
					these = new ArrayList<Formatter>();
					theseTypes.append(lastType);
					theseTypes.append("\',\'");
				}
				these.add(fmt);					
				lastType = ef.getEventType();
			} catch (NoSuchBeanDefinitionException e) {
				e.printStackTrace();
				//TODO
			}
		}
		formatters.put(lastType, these);
		theseTypes.append(lastType);
		theseTypes.append("\',\'");
		setOurTypes(theseTypes.substring(0,theseTypes.length()-2));
	}

	//getEventDao();
	/* (non-Javadoc)
	 * @see com.db.gffxo.epi.controller.FormatControllerServices#getEventDao()
	 */
	public EventDao getEventDao() {
		return eventDao;
	}

	//setEventDao(rs.getEventDao(10));
	/* (non-Javadoc)
	 * @see com.db.gffxo.epi.controller.FormatControllerServices#setEventDao(com.db.gffxo.epi.repository.EventDao)
	 */
	public void setEventDao(EventDao eventDao) {
		this.eventDao = eventDao;
	}

	//getEventFormatDao();
	/* (non-Javadoc)
	 * @see com.db.gffxo.epi.controller.FormatControllerServices#getEventFormatDao()
	 */
	public EventFormatDao getEventFormatDao() {
		return eventFormatDao;
	}

	//setEventFormatDao(rs.getEventFormatDao(10));
	/* (non-Javadoc)
	 * @see com.db.gffxo.epi.controller.FormatControllerServices#setEventFormatDao(com.db.gffxo.epi.repository.EventFormatDao)
	 */
	public void setEventFormatDao(EventFormatDao eventFormatDao) {
		this.eventFormatDao = eventFormatDao;
	}

	//getEventDetailDao();
	/* (non-Javadoc)
	 * @see com.db.gffxo.epi.controller.FormatControllerServices#getEventDetailDao()
	 */
	public EventDetailDao getEventDetailDao() {
		return eventDetailDao;
	}

	//setEventDetailDao(rs.getEventDetailDao(10));
	/* (non-Javadoc)
	 * @see com.db.gffxo.epi.controller.FormatControllerServices#setEventDetailDao(com.db.gffxo.epi.repository.EventDetailDao)
	 */
	public void setEventDetailDao(EventDetailDao eventDetailDao) {
		this.eventDetailDao = eventDetailDao;
	}


	public String getOurTypes() {
		return ourTypes;
	}


	public void setOurTypes(String ourTypes) {
		this.ourTypes = ourTypes;
	}


}
